import { Vector3 } from "three";
import Polygon from "../models/Polygon";

export default class PolygonMeasureAnalysis {
    private polgyon: Polygon;

    constructor(polygon: Polygon) {
        this.polgyon = polygon;
    }

    /**
     * 计算多边形的面积
     * @returns 返回的面积是以平方米为单位
     */
    public calculateArea() {
        let bufferGeometry = this.polgyon.geometry;
        var area = 0;
        var positionAttribute = bufferGeometry.attributes.position;
        var indices = bufferGeometry.index;
    
        if (!indices) {
            // 如果没有索引，那么我们假设几何体是按顺序排列的三角形
            for (var i = 0; i < positionAttribute.count; i += 3) {
                var a = new Vector3().fromBufferAttribute(positionAttribute, i);
                var b = new Vector3().fromBufferAttribute(positionAttribute, i + 1);
                var c = new Vector3().fromBufferAttribute(positionAttribute, i + 2);
    
                var ab = a.distanceTo(b);
                var bc = b.distanceTo(c);
                var ca = c.distanceTo(a);
                var s = (ab + bc + ca) / 2;
                area += Math.sqrt(s * (s - ab) * (s - bc) * (s - ca));
            }
        } else {
            // 使用索引来遍历三角形
            for (var i = 0; i < indices.count; i += 3) {
                var aIndex = indices.getX(i);
                var bIndex = indices.getX(i + 1);
                var cIndex = indices.getX(i + 2);
    
                var a = new Vector3().fromBufferAttribute(positionAttribute, aIndex);
                var b = new Vector3().fromBufferAttribute(positionAttribute, bIndex);
                var c = new Vector3().fromBufferAttribute(positionAttribute, cIndex);
    
                var ab = a.distanceTo(b);
                var bc = b.distanceTo(c);
                var ca = c.distanceTo(a);
                var s = (ab + bc + ca) / 2;
                area += Math.sqrt(s * (s - ab) * (s - bc) * (s - ca));
            }
        }
    
        area = Number(area.toFixed(2));
        return area;
    }

    /**
     * 计算周长
     * @returns 返回的周长以米为单位
     */
    public calculatePerimeter() {
        let pointArray = this.polgyon.data.pointArray;
        let perimeter = 0;
        for (let i = 0; i < pointArray.length - 1; i++) {
            perimeter += pointArray[i].distanceTo(pointArray[i + 1]);
        }

        perimeter = Number(perimeter.toFixed(2));
        return perimeter;
    }
}